Music-Timer
Music Timer is a crate with music time and counting utilities featuring a callback performance engine to help with triggering events in music time. Written in Rust.
Its aims are to allow for an easy interface to trigger events in music time. This crate does not feature any threading.
Performance engine
To create a performance engine with a time signature and bpm call music_timer::create_performance_engine
.
let mut performer = music_timer::create_performance_engine(3, 4, 155.0);
Create a struct
with the trait MusicTimerState
and pass it into the engine's pulse. The callbacks will be triggered in music time.
struct PerformanceState;
impl MusicTimerState for PerformanceState {
fn on_beat_interval(&mut self, current_time: &MusicTime) {
}
fn on_beat(&mut self, current_time: &MusicTime) {
}
fn on_bar(&mut self, current_time: &MusicTime) {
}
}
let mut performer_state = PerformanceState{};
let mut performer = music_timer::create_performance_engine(3, 4, 155.0);
performer.pulse(&mut performer_state);
Future work
- Support un orthodox time signatures e.g 3/5.
- Explore the need for higher resolution beat intervals.
Example
use music_timer::{
music_time::MusicTime,
music_timer_engine::MusicTimerState,
};
struct PerformanceState {
is_playing: bool,
performance_end: MusicTime,
events: Vec<MusicTime>,
event_head: usize,
}
impl MusicTimerState for PerformanceState {
fn on_beat_interval(&mut self, current_time: &MusicTime) {
let event_triggered =
self.event_head < self.events.len() && *current_time == self.events[self.event_head];
if event_triggered {
self.event_head += 1;
}
println!(
"{:02}.{}.{} = {}",
current_time.get_bar(),
current_time.get_beat(),
current_time.get_beat_interval(),
event_triggered
);
self.is_playing = *current_time < self.performance_end;
}
fn on_beat(&mut self, _current_time: &MusicTime) {
}
fn on_bar(&mut self, _current_time: &MusicTime) {
}
}
fn main() {
use std::thread;
let mut performer_state = PerformanceState {
is_playing: true,
performance_end: MusicTime::new(4, 3, 8),
events: vec![
MusicTime::new(1, 1, 1),
MusicTime::new(2, 2, 5),
MusicTime::new(4, 3, 8),
],
event_head: 0,
};
let mut performer = music_timer::create_performance_engine(3, 4, 155.0);
let sleep_duration = performer.get_beat_interval_duration() / 2;
println!("SLEEP_DURATION: {:?}", sleep_duration);
while performer_state.is_playing {
performer.pulse(&mut performer_state);
thread::sleep(sleep_duration);
}
}